package org.example.repeater.handler;

import com.github.benmanes.caffeine.cache.Cache;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.ByteBufUtil;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import org.example.repeater.handler.core.Bit;
import org.example.repeater.message.pushChannel;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.List;

import static org.example.repeater.message.Constant.*;

public class deviceHandler extends ChannelInboundHandlerAdapter {
    private static final Logger log = LoggerFactory.getLogger(deviceHandler.class);
    private  List<ChannelHandlerContext> clientContext;//所有上级连接
    private Cache<String, Object> caffeineCache;
    private List<String> findIp;
    private  String sim;
    private ChannelHandlerContext ctx;
    public deviceHandler(Cache<String, Object> caffeineCache) {
        this.caffeineCache = caffeineCache;
    }
    public void addClientContext(ChannelHandlerContext client,String address){
        clientContext.add(client);
        caffeineCache.put(devicePref+address,this.ctx);
    }

    @Override
    public void channelRead(ChannelHandlerContext ctx, Object msg) {
        ByteBuf buf = (ByteBuf) msg;
        if (sim==null){
            getSim(buf);
            this.ctx=ctx;
        }
        if (clientContext==null||clientContext.isEmpty()){
            clientContext= pushChannel.getInstance(caffeineCache).getClientContext(sim,ctx);
        }
        if (!clientContext.isEmpty()){
            clientContext.forEach(server->{
                log.info("终端>>>>>>{}[{}]",server.channel().remoteAddress(), ByteBufUtil.hexDump(buf));
                buf.retain();
                server.writeAndFlush(buf);
            });
            buf.release();
        }
    }





    private  void getSim(ByteBuf buf) {
        buf.markReaderIndex();
        int properties = buf.getUnsignedShort(2);
        int version = 0;//缺省值为2013版本
        StringBuilder tempSim =new StringBuilder();
        buf.skipBytes(5);
        if (Bit.isTrue(properties, 14)){
            //识别2019及后续版本
            version = buf.getUnsignedByte(4);
            for (int i = 0; i < 10; i++) {
                int val = buf.readUnsignedByte();
                int ch1 = (val >> 4) & 0x0F;
                int ch2 = val & 0x0F;
                tempSim.append(ch1 + Integer.toString(ch2));
            }
        }
        else{
            for (int i = 0; i < 6; i++) {
                int val = buf.readUnsignedByte();
                int ch1 = (val >> 4) & 0x0F;
                int ch2 = val & 0x0F;
                tempSim.append(ch1 + Integer.toString(ch2));
            }
        }
        sim= tempSim.toString().replaceFirst("^0*", "");
        caffeineCache.put(deivceHandlerPref+sim,this);
        findIp = pushChannel.getInstance(caffeineCache).findCtxByIp(sim);
        buf.resetReaderIndex();
    }

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        log.error("终端连接出现异常，原因如下:{}",cause.getCause());
        cause.printStackTrace();
        release();
    }

    @Override
    public void channelInactive(ChannelHandlerContext ctx) throws Exception {
        super.channelInactive(ctx);
        release();
    }

    public void release() {
        if (sim != null) {
            caffeineCache.invalidate(deivceHandlerPref+sim);
            List<String> findIp = pushChannel.getInstance(caffeineCache).findCtxByIp(sim);
            findIp.forEach(ip->{
                caffeineCache.invalidate(devicePref+ip);
            });
            log.info("设备:{},断开连接",sim);
            sim=null;
        }
    }
}
